import { Ref, useState, useRef, useEffect, useContext, useMemo } from 'react';
import { Button, Table, message, Form, Row, Col, Select, Input, Spin, Steps } from 'antd';
import lodash from 'lodash';

import { UpdatePlanListCard } from './UpdatePlanListCard';

import { PlanManageTab } from '../mconfig';
import { ApplyUpdateContext } from '../common/ApplyContext';
import { getMaterialTableColumns } from '../mconfig/PackTableColumns';
import { ApplyUpdateService } from '../services/UpdateService';
import { PlanMaterialInfoServices } from '../services/PlanService';
import { formatDecimal, getNowData, onMouseOut_ANTDBTN, setTableRowClassName } from '../common/Format';

import { OneModal } from '@/components/one-ui';
import { IOneModalRef } from '@/pages/type';
import Cls from 'classnames';
import { getLoadMapList, getTenantID, onCloseModalCommon } from '@/utils';
import { ReloadOutlined, SearchOutlined, FileDoneOutlined, FileSearchOutlined } from '@ant-design/icons';
import { commonPageSizeOptions, showTotalInfo } from '@/common/constVariable';
import { ILoadMapTypeAll } from '@/common';
import { UpdateMaterialCollectData } from './UpdateMaterialCollectData';
import { ApplyUpdateAPI } from '../common/type';

/**
 * @UpdateMaterialModal 添加标的信息
 * @param successMaterials 已经分包的标的
 * @param onClose 关闭弹窗组件
 * @param onSave 保存事件
 * @returns
 */
const UpdateMaterialModal: React.FC<ApplyUpdateAPI.IUpdateNeedMaterialModal> = ({ successMaterials = [], onClose, onSave, selectMaterialList }) => {
  /** 上下文 */
  const { prefixCls, curRes } = useContext(ApplyUpdateContext);
  /** 弹框Ref */
  const reloadLayoutRef: Ref<IOneModalRef> = useRef(null);
  /** 表单实例 */
  const [searchForm] = Form.useForm();
  /** 字典编码 */
  const loadMdicIds: string[] = [`${getTenantID()}${ILoadMapTypeAll.PURCHASE_CATEGORY}`];
  /** 请求字典services */
  const { loadMapInfo: loadMdicMapList, mapLoading } = getLoadMapList(loadMdicIds);
  /** 右侧表格选中行的key */
  const [selectedRowKeys, setSelectedRowKeys] = useState<React.Key[]>([]);
  /** 右侧表格选中行内容 */
  const [selectedRows, setSelectedRows] = useState<Record<string, any>[]>([]);
  /** 右侧表格数据 */
  const [dataSource, setDataSource] = useState<Record<string, any>[]>([]);
  /** 左侧选中树的key */
  const [selectKeys, setSelectKeys] = useState<React.Key[]>([]);
  /** 左侧类型树搜索 */
  const [typeTreeSearchObj, setTypeTreeSearchObj] = useState<Record<string, any>>({
    searchValue: '',
    expandedKeys: [],
  });
  /** 存储一份选择table的数据 */
  const [handleData, setHandleData] = useState<Record<string, any>>([]);

  /** 步骤条位置 */
  const [currentStep, setCurrentStep] = useState(0);
  /** 步骤条渲染步骤 */
  const stepsItems = [
    { title: '选择标的', key: 'select-pack', icon: <FileSearchOutlined /> },
    { title: '确认信息', key: 'comfirm-msg', icon: <FileDoneOutlined /> },
  ];

  /** 计划列表 - services */
  const { getPlanListRun, getPlanListDataSource, getPlanListLoading, getPlanListTableProps } = PlanMaterialInfoServices()?.getPlanListService();

  /** 物料表格 - services */
  const { findNeedMaterialService } = ApplyUpdateService();
  const { findNeedMaterialRun, findNeedMaterialLoading, findNeedMaterialProps } = findNeedMaterialService((res) => {
    if (res?.msgFlag) {
      // dataComparison(res?.rows, successMaterials);
      dataComparison(res?.rows, selectMaterialList);
      message.success(res?.msg);
    } else {
      message.warning(res?.msg);
    }
  }, curRes);

  /**
   * @dataComparison 数据同步，根据已选数据，与 查询数据做对比，更新已采数量与预估总价
   * @param originData 接口获取的数据
   */
  const dataComparison = (originData: Record<string, any>[], seleMList: any[]) => {
    seleMList.forEach((susItems) => {
      originData.forEach((item) => {
        if (susItems?.needID == item?.needID && susItems?.materialID == item?.materialID) {
          if (susItems?.newExpectNum != 0) {
            // item.lockNum = Number(susItems?.expectNum);
            item.lockNum = Number(item.lockNum) + Number(susItems?.newExpectNum);
          }
        }
      });
    });

    originData?.forEach((item) => {
      /** 有物料信息存在，就将需要的字段给到上一层，便于table展示数据 */
      if (item?.mmaterialList?.[0]) {
        let materialObj = item?.mmaterialList?.[0]; /** 物料对象 */
        item.fullName = materialObj?.fullName; /** 标的名称 */
        // item.supplyTypeName = materialObj?.supplyTypeName; /** 标的类型 */
        item.supplyType = materialObj?.supplyType;
        item.specInfo = materialObj?.specInfo; /** 规格型号 */
      }

      /** 判断有没有【orderApplyNum】属性 ,没有说明上面的successMaterials是空数组没有执行*/
      if ('orderApplyNum' in item) {
      } else {
        item.orderApplyNum = 0;
      }

      item.needMID = item?.id;

      if (!selectedRows?.length) {
        // 初始的时候要显示
        item.inpNum = Number(item?.prepareNum || 0) - Number(item?.lockNum || 0);
      } else {
        const resobj = selectedRows?.find((ite) => ite?.needID == item?.needID && ite?.materialID == item?.materialID);
        if (resobj) {
          item.inpNum = resobj?.inpNum || Number(item?.prepareNum || 0) - Number(item?.lockNum || 0);
        } else {
          item.inpNum = Number(item?.prepareNum || 0) - Number(item?.lockNum || 0);
        }
      }

      item.expectPrice = formatDecimal(item?.expectPrice);
      item.expectSum = formatDecimal(item?.expectSum);
    });

    setDataSource(originData);
  };

  /** 根据计划id获取需求物料列表 */
  useEffect(() => {
    /** 获取左侧计划列表数据 */
    getPlanListRun({ ...PlanManageTab(curRes), current: 1, pageSize: 10 });
    /** 获取右侧Table数据列表 【TODO: 梁豪杰 计划id 临时默认：[fetchFindNeedMaterial({ planID: '8368097756643446784' })]】 */
    findNeedMaterialRun({});
  }, [curRes]);

  useEffect(() => {}, [selectedRows]);

  const PlanIdsMemo = useMemo(() => {
    if (selectedRows?.length) {
      let PlanIDS: any[] = selectedRows?.map((item) => item?.planID);
      return Array.from(new Set(PlanIDS));
    } else {
      return [];
    }
  }, [selectedRows]);

  /** 表格复选框配置 */
  const rowSelection = {
    selectedRowKeys,
    onSelect: (record: any, selected: any) => {
      if (selected) {
        /** 添加 */
        setSelectedRowKeys([...selectedRowKeys, record?.id]); // 保存key
        setSelectedRows([...selectedRows, record]); // 保存record
      } else {
        /** 去除 */
        const rowsList = selectedRows?.filter((item) => record?.id != item?.id);
        setSelectedRowKeys(rowsList?.map((i: Record<string, any>) => i?.id));
        setSelectedRows(rowsList);
      }
    },
    onSelectAll: (selected: any, selectedRow: any, changeRows: any) => {
      let dataKeys: any[] = []; // 当前table渲染的数据key集合
      dataSource?.forEach((item: Record<string, any>) => {
        if (Number(item?.prepareNum || 0) - Number(item?.lockNum || 0) > 0) {
          dataKeys?.push(item?.id);
        }
      });
      if (selected) {
        //全选
        // 两个key合并去重
        let keylist = Array.from(new Set([...dataKeys, ...selectedRowKeys]));
        setSelectedRowKeys(keylist);
        // 处理record
        setSelectedRows([...selectedRows, ...changeRows]);
      } else {
        //全不选
        // 处理key
        let newarr: any[] = selectedRowKeys?.filter((item) => {
          return !dataKeys?.includes(item);
        });
        setSelectedRowKeys(newarr);
        /**
         * 处理row 这里的changeRows代表被取消的rows集合
         * {keys} 拿的是被取消的rows集合的id集合
         * 再已经选择的数据中进行过滤
         * */
        let keys: any[] = [];
        changeRows?.forEach((item: any) => {
          keys?.push(item?.id);
        });
        const newRows = selectedRows?.filter((item) => {
          return keys?.indexOf(item?.id) == -1;
        });
        setSelectedRows(newRows);
      }
    },
    getCheckboxProps: (record) => ({
      /** 跟Modal中的Table的column一样 当待采数量为0就不让操作 */
      disabled: Number(record?.prepareNum || 0) - Number(record?.lockNum || 0) <= 0,
    }),
  };

  /** 抛出标的信息 */
  const submit = () => {
    onSave({ mpurchaseNeedMaterials: handleData });
    onCloseModalCommon(reloadLayoutRef);
  };

  /**  @onEditTable 物料表格编辑事件  @param value 修改后的值 @param type 修改元素标签类型， 区分标签做不同的数据修改 @param key 表格key值 @param record 表格单条数据*/
  const onEditTable = ({ value, type, key, record }: Record<string, any>) => {
    const index = dataSource.findIndex((item: Record<string, any>) => item.id == record.id);
    const selectedRowsIndex = selectedRows.findIndex((item: Record<string, any>) => item.id == record.id);
    const currentData = lodash.cloneDeep(dataSource);
    if (type == 'switch') {
      currentData[index][key] = Number(value);
    } else if (type == 'InputNumber') {
      /** 修改表格【数量】。重新计算预告总价 */
      if (key == 'prepareNum') {
        currentData[index].inpNum = value; // 显示使用
        // currentData[index].expectSum = ((value as number) * record.expectPrice).toFixed(2);
        setDataSource(currentData);
        /** 做一个同步，处理选中之后在更改数量，导致的结果导出后还是未修改前的数据 */
        if (selectedRowsIndex != -1) {
          const newSelectedRows = lodash.cloneDeep(selectedRows);
          newSelectedRows[selectedRowsIndex].inpNum = value;
          setSelectedRows(newSelectedRows);
        }
      }
    }
  };

  const [isNextBtn, setisNextBtn] = useState(false);

  const setisNextBtnFun = (isNextBtn: boolean) => {
    setisNextBtn(isNextBtn);
  };

  /** 表格操作按钮 */
  const modalFooterRender = () => {
    return (
      <>
        {currentStep == 0 ? (
          <Button onClick={() => onCloseModalCommon(reloadLayoutRef)}>取消</Button>
        ) : (
          <Button onClick={() => setCurrentStep(0)}>上一步</Button>
        )}
        {currentStep == 0 ? (
          <Button
            onClick={() => {
              let newselectedRows = selectedRows?.map((item) => {
                return {
                  ...item,
                  expectNum: item?.inpNum, //方法计算使用expectNum字段，将input框内容的值赋值给该字段
                };
              });
              setHandleData(newselectedRows);
              setCurrentStep(1);
            }}
            disabled={selectedRowKeys?.length === 0 || isNextBtn}
          >
            下一步
          </Button>
        ) : (
          <Button type={'primary'} onClick={submit}>
            确认
          </Button>
        )}
      </>
    );
  };

  /** 分页方法 */
  const handlePaginationChange = (current: any, pageSize: any, params: any) => {
    findNeedMaterialRun({ pageSize, current, ...params, ...searchForm.getFieldsValue(), planID: selectKeys?.toString() || null });
  };

  return (
    <>
      <OneModal
        open={true}
        getContainer={false}
        ref={reloadLayoutRef}
        title={'标的信息列表'}
        width={document.documentElement.clientWidth * 0.9}
        onCancel={onClose as any}
        footer={modalFooterRender()}
        centered
        bodyStyle={{
          height: document.documentElement.clientHeight * 0.8,
          // height: '250px',
          padding: '10px 20px',
          overflow: 'hidden',
          display: 'flex',
          flexDirection: 'column',
        }}
      >
        <div className={prefixCls + '-selectPackAgeTopTitle'}>
          <Steps
            size={'default'}
            current={currentStep}
            items={stepsItems}
            // onChange={(current) => setCurrentStep(current)}
          />
        </div>
        {currentStep == 0 ? (
          <div style={{ flex: 'auto', overflow: 'hidden' }}>
            <Row gutter={[10, 16]} className={prefixCls + '-selectPackageModal'}>
              {/* 左侧计划选择列表 */}
              <Col span={7}>
                <Spin spinning={getPlanListLoading}>
                  <UpdatePlanListCard
                    onSelect={(val) => findNeedMaterialRun({ planID: val, ...searchForm.getFieldsValue() })}
                    onChange={{ selectKeys, setSelectKeys, typeTreeSearchObj, setTypeTreeSearchObj }}
                    dataSource={getPlanListDataSource}
                    PlanIdsMemo={PlanIdsMemo}
                    loading={getPlanListLoading}
                    getPlanSev={() => {
                      let { current, pageSize, total }: Record<string, any> = getPlanListTableProps?.pagination;
                      /** 避免多次请求 */
                      if (getPlanListDataSource?.length < total) {
                        getPlanListRun({ ...PlanManageTab(curRes), current, pageSize: pageSize + 10 });
                      }
                    }}
                  />
                </Spin>
              </Col>

              {/* 右侧需求物料Table */}
              <Col
                span={17}
                style={{
                  display: 'flex',
                  overflow: 'hidden',
                  flexDirection: 'column',
                }}
                className={prefixCls + '-selectPackageModal-rightBox'}
              >
                <Spin spinning={findNeedMaterialLoading}>
                  <div style={{ padding: '8px 0 0' }}>
                    <Form form={searchForm}>
                      <Row>
                        <Col span={5}>
                          <Form.Item name={'fullName'}>
                            <Input placeholder="标的名称" allowClear />
                          </Form.Item>
                        </Col>
                        <Col span={5} style={{ paddingLeft: '8px' }}>
                          <Form.Item name={'supplyType'}>
                            <Select
                              placeholder="标的类型"
                              options={[
                                {
                                  value: `${getTenantID()}${ILoadMapTypeAll.PURCHASE_CATEGORY}1003`,
                                  label: '材料类',
                                },
                                {
                                  value: `${getTenantID()}${ILoadMapTypeAll.PURCHASE_CATEGORY}1004`,
                                  label: '资产类',
                                },
                                {
                                  value: `${getTenantID()}${ILoadMapTypeAll.PURCHASE_CATEGORY}1001`,
                                  label: '服务类',
                                },
                                {
                                  value: `${getTenantID()}${ILoadMapTypeAll.PURCHASE_CATEGORY}1002`,
                                  label: '工程类',
                                },
                              ]}
                            />
                          </Form.Item>
                        </Col>
                        <Col span={5} style={{ paddingLeft: '8px' }}>
                          <Form.Item name={'needParams'}>
                            <Input placeholder="规格要求（参数）" allowClear />
                          </Form.Item>
                        </Col>
                        <Col span={9} style={{ display: 'flex', justifyContent: 'flex-end' }}>
                          <Form.Item>
                            <Button
                              type={'default'}
                              icon={<ReloadOutlined />}
                              onClick={() => {
                                /** 重置表单 */
                                searchForm.resetFields();
                                /** 重新请求 */
                                findNeedMaterialRun({});
                              }}
                              onMouseOut={onMouseOut_ANTDBTN}
                              style={{ marginRight: 0, float: 'right' }}
                            >
                              重置
                            </Button>
                            <Button
                              type={'primary'}
                              icon={<SearchOutlined />}
                              onClick={() => {
                                findNeedMaterialRun({
                                  planID: selectKeys?.toString() || null,
                                  ...searchForm.getFieldsValue(),
                                });
                              }}
                              onMouseOut={onMouseOut_ANTDBTN}
                              style={{ marginRight: '8px', float: 'right' }}
                            >
                              查询
                            </Button>
                          </Form.Item>
                        </Col>
                      </Row>
                    </Form>
                  </div>
                  {/* <div className={'list-table selectPackageTable'}> */}
                  <div className={Cls('list-table', 'selectPackageTable')}>
                    <Table
                      size="small"
                      bordered={true}
                      scroll={{ x: 1300, y: 1000 }}
                      style={{ margin: '0' }}
                      rowClassName={setTableRowClassName}
                      dataSource={dataSource}
                      rowSelection={rowSelection}
                      columns={getMaterialTableColumns({ onEditTable, setisNextBtnFun })}
                      pagination={{
                        showQuickJumper: true,
                        showSizeChanger: true,
                        pageSizeOptions: commonPageSizeOptions,
                        showTotal: (total: any, range: any) => {
                          return (
                            <>
                              <div
                                style={{
                                  display: 'flex',
                                  width: '100%',
                                  justifyContent: 'space-between',
                                  marginTop: -2,
                                }}
                              >
                                <div>
                                  <span>
                                    已选择<a style={{ fontWeight: 700 }}> {PlanIdsMemo?.length} </a>计划中的
                                    <a style={{ fontWeight: 700 }}> {selectedRowKeys?.length} </a>个标的
                                  </span>
                                </div>
                                <div>{showTotalInfo(total, range)}</div>
                              </div>
                            </>
                          );
                        },
                        onChange: handlePaginationChange as any,
                        pageSize: findNeedMaterialProps?.pagination?.pageSize,
                        current: findNeedMaterialProps?.pagination?.current,
                        total: findNeedMaterialProps?.pagination?.total,
                      }}
                      rowKey={'id'}
                    />
                  </div>
                </Spin>
              </Col>
            </Row>
          </div>
        ) : (
          <UpdateMaterialCollectData dataSource={handleData} />
        )}
      </OneModal>
    </>
  );
};

export default UpdateMaterialModal;
